说明:从
Xcode 3.2
开始加入的新功能,不需要运行程序就可以从逻辑上检测代码的工具,它可以寻找会演变成bug的错误。
19.1 静态工作
说明:
静态分析器
可以识别以下几种错误
- 安全问题:比如内存泄漏和缓冲区溢出
- 并发性问题:比如静态条件(也就是依赖时间的两个或多个任务失效)
- 逻辑问题:包括废代码和不好的编码习惯
注意:
静态分析器
存在以下不足
- 拖慢构建程序的过程:因为需要消耗时间来进行分析
- 有时会误报错误
- 需要适应:因为改变了熟悉的工作流程
19.1.1 开始分析
运行静态分析器:
Product(菜单) -> Analyze
,分解决过在导航栏issue
中可以看到
19.1.1.1 废代码
废代码:创建了一个对象
pool
,但从没有在代码中直接访问过,没有向它发送消息也没有更改过它。
优化手段:移除废代码
优化意义:废代码并不一定会给程序带来功能上的问题,但终归会浪费性能,移除废代码可以使应用程序更加高效。
19.1.1.2 内存泄漏:对象被释放之前程序return
说明:通常还没有释放掉分配的内存的对象,就过早返回时便会出现这种情况。
扩展:可以通过点击带有分析器图标
的代码来观察代码从开始到当前行的运行流程
- 触发“运行流程”
- 完毕
19.1.1.3 内存泄漏:副本没有释放
说明:创建一个对象的副本,要在适当的时候对其进行释放,否则引发内存泄漏。
优化手段:在main
函数结尾处释放carCopy
。
19.1.1.4 内存泄漏:description方法中的desc在返回前没有释放
说明:
AllWeatherRadial类
中的description
方法中分配了一个字符串desc
,但没有在返回函数之前释放它。
1 | - (NSString *) description |
19.1.2 协助分析器
说明:
静态分析器
分析出的“问题”如果是我们有意的,可以通过在声明方法时使用一些关键字
避免误报;或者有些情况下,想要使通常没问题的方式发出警报。比如
关键字 | 用途 | 对应的惯例 | 返回对象为Core Foundation 对象时 |
---|---|---|---|
NS_RETURNS_RETAINTED |
标记方法,以返回一个保留计数器的值不是零的对象 | 分配内存的地方也要负责清理内存 | CF_RETURNS_RETAINTED |
NS_RETURNS_NOT_RETAINED |
使静态分析器 在方法试图返回一个保留对象时发出issue |
返回保留对象通常不需要做额外内存管理 | NS_RETURNS_NOT_RETAINED |
CLANG_ANALYZER_NORETURN |
如果方法有值返回,就在静态分析 是发出警报 |
方法返回值不会发生issue |
无意义 |
NS_RETURNS_RETAINTED:返回一个保留的对象
1 | - (NSMutableArray *) superDuperArrayCreator NS_RETURNS_RETAINED; |
1 | - (NSMutableArray *) superDuperArrayCreator |
NS_RETURNS_NOT_RETAINED:返回一个未保留的对象
1 | // 分析器会在该方法视图返回一个保留对象时提出issue |
19.1.3 了解更多
说明:
静态分析器
能够找到的其它问题
issue |
说明 | 解决issue |
---|---|---|
等号错误 | if (myValue = expression) 存在歧义 |
赋值后判空:if ((myValue = expression)) ;判等:if (nil != (myValue = expression)) |
内存泄漏 | 方法中的运行时错误使方法提前return,导致release代码没有执行而发生内存泄漏 | 无论什么时候退出了方法,都需要确认有没有分配了单海没有释放的对象 |
过度释放 | 重复autorelease |
移除多余的autorelease |
@synchronized语句中的空值 |
@synchronized(object) 中的object 如果为nil 就发出issue |
确保object 不为nil |
建议:把
静态分析器
作为一个善意但烦人的朋友,因为它所说的通常都是对的。
注意:不要太依赖静态分析器
来查找每一个内存泄漏和废代码,自己要对自己的代码负责。